#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <openssl/bio.h>
#include <openssl/evp.h>
#include <openssl/buffer.h>

// Base64 编码函数
char* base64_encode(const unsigned char* input, int len) {
    BIO *bmem, *b64;
    BUF_MEM *bptr;

    b64 = BIO_new(BIO_f_base64());
    bmem = BIO_new(BIO_s_mem());
    b64 = BIO_push(b64, bmem);
    BIO_write(b64, input, len);
    (void)BIO_flush(b64);
    BIO_get_mem_ptr(b64, &bptr);

    char *buff = (char *)malloc(bptr->length + 1);
    memcpy(buff, bptr->data, bptr->length);
    buff[bptr->length] = '\0';

    BIO_free_all(b64);
    return buff;
}

// Base64 解码函数
unsigned char* base64_decode(const char* input, int* len) {
    BIO *b64, *bmem;
    size_t input_len = strlen(input);
    unsigned char *buffer = (unsigned char*)malloc(input_len);
    memset(buffer, 0, input_len);

    b64 = BIO_new(BIO_f_base64());
    bmem = BIO_new_mem_buf(input, input_len);
    bmem = BIO_push(b64, bmem);

    *len = BIO_read(bmem, buffer, input_len);
    BIO_free_all(bmem);

    return buffer;
}

int main() {
    // 读取 sn.txt
    FILE *fp = fopen("sn.txt", "rb");
    if (!fp) {
        perror("无法打开 sn.txt");
        return 1;
    }

    fseek(fp, 0, SEEK_END);
    long fsize = ftell(fp);
    fseek(fp, 0, SEEK_SET);

    char *content = malloc(fsize + 1);
    fread(content, 1, fsize, fp);
    content[fsize] = '\0';
    fclose(fp);

    printf("原始内容: %s\n", content);

    // 编码
    char *encoded = base64_encode((unsigned char*)content, fsize);
    printf("Base64 编码: %s", encoded);  // openssl 自动加换行，可用 strip 处理

    // 解码
    int decoded_len;
    unsigned char *decoded = base64_decode(encoded, &decoded_len);
    printf("Base64 解码: %.*s\n", decoded_len, decoded);

    // 写入文件（可选）
    FILE *out = fopen("sn_encoded.txt", "w");
    fputs(encoded, out);
    fclose(out);

    out = fopen("sn_decoded.txt", "wb");
    fwrite(decoded, 1, decoded_len, out);
    fclose(out);

    // 释放内存
    free(content);
    free(encoded);
    free(decoded);

    return 0;
}
